<!--
 * @Description: 图片批量上传
 * @Date: 2019-11-29 11:06:55
 * @LastEditTime: 2021-06-08 14:19:11
 -->
<template>
  <div id="batchUpload">
    <Dialog
      :title="watermarkTypeChoose()+'批量上传'"
      width="504px"
      v-model="showDialog"
      custom-class="batch-upload-dialog"
      :beforeClose="closeShowdialog"
    >
      <div class="wrapper" slot="content">
        <div class="upload-wrap">
          <el-upload
            ref="Upload"
            action
            accept=".bmp, .jpg, .jpeg, .png, .pdf, .ofd"
            :http-request="handleUpload"
            :before-upload="handleBeforeUpload"
            :on-exceed="handleExceed"
            :multiple="true"
            :limit="100"
            :show-file-list="false"
          >
            <el-button slot="trigger" icon="el-icon-plus" type="primary" size="small" style="width:115px;height:34px;border-radius:0;">
              选择泄密样本
            </el-button>
            <el-popover
              placement="bottom"
              popper-class="upload-clear-popover"
              trigger="hover"
              content="清除已完成"
            >
              <i v-show="fileList.length > 0" slot="reference" class="el-icon-delete delete" @click="handleClearFileList" />
            </el-popover>
          </el-upload>
          <!-- / 图片上传 -->
          <div class="scroll-wrap">
            <el-scrollbar v-if="fileList.length > 0">
              <ul class="file-list">
                <li v-for="(item,index) in fileList" :key="index" class="file-item">
                  <div class="left" v-if="['pdf', 'ofd'].includes(item.name.split('.')[item.name.split('.').length - 1])">
                    <img src="" alt="">
                  </div>
                  <div class="left" v-else>
                    <img src="" alt="">
                  </div>
                  <div class="right">
                    <div class="name-status">
                      <p class="img-name" :title="item.name">
                        {{ item.name }}
                      </p>
                      <div class="status">
                        <transition name="el-zoom-in-center">
                          <div v-if="item.status !== 0" class="status-wrap">
                            <p v-if="item.status === 1" class="status-text">
                              <img src="" alt="">
                              <span>上传成功</span>
                            </p>
                            <p v-if="item.status === 2" class="status-text">
                              <img src="" alt="">
                              <span>上传失败</span>
                            </p>
                            <p v-if="item.status === 3" class="status-text">
                              <img class="is-repeat" src="" alt="">
                              <span v-if="['pdf', 'ofd'].includes(item.name.split('.')[1])">文件已存在</span>
                              <span v-else>图片已存在</span>
                            </p>
                            <el-popover
                              placement="bottom"
                              popper-class="upload-clear-popover"
                              trigger="hover"
                              :content="item.status === 0 ? '取消' :'删除'"
                            >
                              <i v-if="item.status === 0" slot="reference" class="operate el-icon-close" @click="handleRemove(item)" />
                              <i v-else slot="reference" class="operate el-icon-close" @click="handleRemove(item)" />
                            </el-popover>
                          </div>
                        </transition>
                      </div>
                    </div>
                    <el-progress
                      v-show="item.status === 0"
                      :percentage="item.percentage"
                      :stroke-width="2"
                      type="line"
                      color="#01c1de"
                    />
                  </div>
                </li>
              </ul>
            </el-scrollbar>
            <div v-else class="empty-wrap">
              <img src="" alt="">
            </div>
          </div>
          <!-- /图片上传列表 -->
        </div>
      </div>
    </Dialog>
  </div>
</template>

<script>
import { mapState, mapActions } from 'vuex'
import { Message } from 'element-ui'
import axios from '@/utils/request'
import { getOrientation, isIE, rotateImage, dataURLtoFile } from '@/utils/tools'
import BMF from '@/utils/browserMd5File'
const bmf = new BMF()
const getFileMD5 = (file) => {
  return new Promise((resolve, reject) => {
    // eslint-disable-next-line handle-callback-err
    bmf.md5(file, (err, md5) => {
      resolve(md5, reject)
    })
  })
}

export default {
  props: {
    value: {
      type: Boolean,
      default: false
    }
  },
  data() {
    return {
      showDialog: false,
      fileList: [], // 控制界面显示
      fileListCopy: [], // 控制文件上传
      currentIndex: 0, // 递归上传的索引
      locking: false,
      uploadEnd: false, // 结束上传
    };
  },
  computed: {
    ...mapState({
      productId: state => state.forensic.productId,
      batchUploading: state => state.forensic.batchUploading
      // forceUploadend: state => state.forensic.forceUploadend
    })
  },
  watch: {
    value(val, oldValue) {
      this.showDialog = val
    },
    showDialog(val, oldValue) {
      this.$emit('input', val)
    }
  },
  methods: {
    ...mapActions({
      getList: "forensic/getList" 
    }),
    // 文件取消上传
    handleAbort(item) {
      this.$alert('是否取消', '温馨提示', {
        confirmButtonText: '确定',
        customClass: 'batchClearUpload',
        callback: action => {
          if (action === 'confirm') {
            this.$refs.Upload.abort(item.file)
            this.$message({
              type: 'success',
              message: '取消成功！'
            });
          }
        }
      });
    },
    // 文件上传
    handleUpload() {
      if (!this.locking) {
        this.locking = true // 锁住避免并发
        this.$store.commit('forensic/setBatchUploading', true)
        const fileItem = this.fileListCopy[this.currentIndex]
        const that = this
        this.handleImageFile(fileItem.file).then(imgFile => {
          const formData = new FormData();
          if(that.productId !== 5){
            formData.append('file', imgFile);
          }else{
            formData.append('file', fileItem.file); 
          }
          formData.append('watermarkType', this.productId)
          axios({
            method: 'post',
            url: '/api/forensicService/v1/uploadFile',
            data: formData,
            onUploadProgress: (even) => {
              const percentage = Math.floor((even.loaded / even.total) * 100);
              this.handleChangeFileList('percentage', percentage)
            }
          }).then((res) => {
            const { data } = res.data
            let status = 1
            if (data.exists === true) status = 3
            this.handleChangeFileList('status', status)
          }).catch(() => {
            this.handleChangeFileList('status', 2)
          }).finally(() => {
            if (!this.uploadEnd) this.locking = false
            this.currentIndex += 1
            if (this.currentIndex !== this.fileListCopy.length && !this.uploadEnd) {
              this.handleUpload()
            } else {
              this.$store.commit('forensic/setBatchUploading', false)
            }
          })
        })
      }
    },
    /**
     * 改变文件列表
     * @param {string} key 需要改变的key
     * @param {string} value 需要改变的value
     * @return: void
     */
    handleChangeFileList(key, value) {
      const md5 = this.fileListCopy[this.currentIndex].md5
      this.fileList.forEach(item => {
        if (item.md5 === md5) {
          item[key] = value
        }
      })
    },
    /**
     * @name: handleFileData
     * @msg: 将图片文件纠正
     * @param {file} file 图片文件流
     * @return: file
     */
    handleImageFile(file) {
      return new Promise((resolve) => {
        getOrientation(file).then(orient => {
          if (orient && orient === 6 && !isIE()) {
            const reader = new FileReader(); const image = new Image()
            reader.readAsDataURL(file)
            reader.onload = (e) => {
              image.src = e.target.result
              image.onload = () => {
                const base64Url = rotateImage(image, image.width, image.height)
                const newFile = dataURLtoFile(base64Url, file.name)
                resolve(newFile)
              }
            }
          } else {
            resolve(file)
          }
        })
      })
    },
    // 文件上传之前
    handleBeforeUpload(file) {
      return getFileMD5(file).then((md5, reject) => {
        const names = file.name.split('.')
        const type = names[names.length - 1].toLocaleLowerCase()
        console.log(names)
        console.log(type)
        const format = ['bmp', 'jpg', 'jpeg', 'png', 'pdf', 'ofd'].includes(type)
        const excludeFormat = ['pdf', 'ofd'].includes(type)
        const isLt100M = file.size / 1024 / 1024 < 100
        let isRepeat = false
        this.fileList.forEach(item => {
          if (item.md5 === md5) isRepeat = true
        })
        if (!format) {
          Message.error({ message: '请选择 jpg、jpeg、png、bmp、pdf、ofd 格式的文件', center: true });
          throw new Error('上传文件格式不正确')
        }else if(this.productId !== 8 && this.productId !== 5 && this.productId !== 7 && excludeFormat){
          Message.error({ message: '请选择 jpg、jpeg、png、bmp 格式的文件', center: true });
          throw new Error('上传文件格式不正确')
        }else if (!isLt100M) {
          Message.error({ message: '暂不支持100M以上文件上传', center: true });
          throw new Error('文件大小超出100M')
        } else if (isRepeat) {
          Message.error({ message: '队列中已存在，已自动去重', center: true });
          throw new Error('文件重复')
        } else {
          const item = {
            name: file.name,
            percentage: 0,
            file: file,
            status: isRepeat ? 3 : 0, // 0未上传 1上传成功 2上传失败 3图片重复
            loading: false,
            md5: md5
          }
          this.fileList.push(item)
          this.fileListCopy.push(item)
        }
      })
    },
    // 文件移除（fileList）
    handleRemove(item) {
      const index = this.fileList.findIndex(ite => {
        return item.name === ite.name
      })
      this.fileList.splice(index, 1)
    },

    // 清空已上传的文件列表
    handleClearFileList() {
      this.$alert('是否清空已上传的文件列表', '温馨提示', {
        confirmButtonText: '确定',
        center: true,
        callback: action => {
          if (action === 'confirm') {
            const array = []
            this.$refs.Upload.clearFiles()
            this.fileList.forEach(item => {
              if (item.status === 0) array.push(item)
            })
            this.fileList = array
            this.$message({
              type: 'success',
              message: '清空成功',
              center: true,
              customClass: 'clearBatchUpload'
            });
          }
        }
      });
    },
    // 路由即将离开
    handleBeforeRouteLeave(to, form, next) {
      if (!this.uploadFlished()) {
        this.$message({
          message: '文件正在上传，请勿跳转页面!',
          type: 'warning'
        });
        next(false)
      } else {
        next()
      }
    },
    //点击关闭按钮关闭dialog
    closeShowdialog(done){
      if(!this.uploadFlished()){
        this.$message({
          message: '泄密样本正在上传中，请勿关闭!',
          type: 'warning'
        });
      }else{
        done()
        this.$refs.Upload.clearFiles()
        this.fileList = []
        this.showDialog = false
        this.getList()
      }
    },
    // 判断文件是否上传完成
    uploadFlished() {
      let isFinlish = true
      this.fileListCopy.forEach(item => {
        if (item.status === 0) isFinlish = false
      })
      this.$store.commit('forensic/setBatchUploading', !isFinlish)
      return isFinlish
    },
    // 文件个数超出
    handleExceed(files, fileList) {
      Message.error({ message: '批量上传文件已达上限', center: true });
    },
    //批量上传水印类型区分
    watermarkTypeChoose() {
    let label = ''
      switch (this.productId) {
          case 1:
          label = 'PC屏幕水印'
          break;
          case 2:
          label = '手机屏幕水印'
          break;
          case 3:
          label = '网页水印'
          break;
          case 4:
          label = '手机原生图片水印'
          break;
          case 5:
          label = '电子文档水印'
          break;
          case 6:
          label = '图片水印'
          break;
          case 7:
          label = '视频水印'
          break;
          case 8:
          label = '终端打印水印'
          break;
          default:
          label = ''
      }
    return label
    },
  }

};
</script>
<style lang="less">
#batchUpload {
  .el-dialog {
		position: absolute;
		top: 0;
		left: 50%;
		margin-left: -252px;
		z-index: 0;
	}
  .wrapper {
    .upload-wrap {
      width: 100%;
      .el-button {
        padding: 8px;
        margin: 0;
      }
      .delete {
        cursor: pointer;
        font-size: 16px;
        outline: none;
        &:hover {
          color: #01c0dd;
        }
      }
      .scroll-wrap {
        height: 400px;
        .el-scrollbar {
          height: 100%;
          width: 100%;
          .el-scrollbar__wrap {
            overflow-x: auto;
            height: 100%;
          }
          .file-list {
            padding-top: 15px;
            .file-item {
              display: flex;
              align-items: center;
              padding: 14px 20px;
              color: #606266;
              transition: all .5s cubic-bezier(.55,0,.1,1);
              border-bottom: solid 1px #ededed;
              &:hover {
                background: #f5f7fa;
              }
              &:hover .operate {
                display: block!important;
              }
              &:hover .status-text {
                display: none!important;
              }
              .left {
                width: 18px;
                img {
                  width: 100%;
                }
              }
              .right {
                width: 399px;
                padding-left: 7px;
                .name-status, .status {
                  display: flex;
                  align-items: center;
                  justify-content: space-between;
                }
                .img-name {
                  width: calc(100% - 130px);
                  font-size: 12px;
                  height: 14px;
                  overflow: hidden;
                  text-overflow: ellipsis;
                  white-space: nowrap;
                  cursor: pointer;
                }
                .status {
                  font-size: 12px;
                  .status-wrap {
                    text-align: right;
                  }
                  .status-text {
                    display: flex;
                    align-items: center;
                    .is-success {
                      color: #01c0dd;
                    }
                    .is-fail {
                      color: #ff7272;
                    }
                    .is-repeat {
                      margin-right: 3px;
                    }
                  }
                }
                .operate {
                  margin-left: 10px;
                  cursor: pointer;
                  font-size: 12px;
                  margin-top: 2px;
                  outline: none;
                  display: none;
                }
                .operate:hover {
                  color: #01c1de;
                }
                .el-progress-bar {
                  padding-right: 40px;
                  width: 100%;
                  margin-right: -40px;
                  box-sizing: border-box;
                }
                .el-progress__text {
                  font-size: 12px!important;
                  margin-left: 8px;
                }
              }
            }
          }
        }
        .empty-wrap {
          display: flex;
          align-items: center;
          justify-content: center;
          width: 100%;
          height: 100%;
          text-align: center;
          img {
            height: 80px;
            margin-top: -24px;
          }
        }
      }
      .el-popover{
        z-index: 2030!important;
      }
    }
    .upload-wrap>div{
      display: flex;
      flex-flow: row wrap;
      align-items: center;
      justify-content: space-between;
      box-sizing: border-box;
      width: 100%;
    }
  }
}
</style>
